/**
 * Auth 模块 API
 * 认证配置相关接口
 */

import { request, type ApiResponse } from "../request";

// ============ 类型定义 ============

/**
 * 签名密钥算法
 */
export type SigningKeyAlgorithm = "EdDSA" | "ES256" | "RS256" | "HS256";

/**
 * 签名密钥状态
 */
export type SigningKeyStatus = "in_use" | "previously_used" | "revoked" | "standby";

/**
 * 签名密钥信息
 */
export interface SigningKey {
	id: string;
	algorithm: SigningKeyAlgorithm;
	status: SigningKeyStatus;
	public_jwk: Record<string, unknown> | null;
	created_at: string;
	updated_at: string;
}

/**
 * 签名密钥列表
 */
export interface SigningKeysResponse {
	keys: SigningKey[];
}

/**
 * 创建签名密钥请求
 */
export interface CreateSigningKeyBody {
	algorithm: SigningKeyAlgorithm;
	status?: SigningKeyStatus;
	private_jwk?: {
		kid?: string;
		use?: string;
		key_ops?: string[];
		ext?: boolean;
		kty?: string;
		alg?: string;
		n?: string;
		e?: string;
		d?: string;
		p?: string;
		q?: string;
		dp?: string;
		dq?: string;
		qi?: string;
	};
}

/**
 * 更新签名密钥状态请求
 */
export interface UpdateSigningKeyBody {
	status: SigningKeyStatus;
}

/**
 * SMS 提供者
 */
export type SmsProvider = "messagebird" | "textlocal" | "twilio" | "twilio_verify" | "vonage";

/**
 * 验证码提供者
 */
export type CaptchaProvider = "turnstile" | "hcaptcha";

/**
 * 密码必需字符要求
 */
export type PasswordRequiredCharacters =
	| "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ:0123456789"
	| "abcdefghijklmnopqrstuvwxyz:ABCDEFGHIJKLMNOPQRSTUVWXYZ:0123456789"
	| "abcdefghijklmnopqrstuvwxyz:ABCDEFGHIJKLMNOPQRSTUVWXYZ:0123456789:!@#$%^&*()_+-=[]{};'\\:\"|<>?,./`~"
	| "";

/**
 * Auth 配置响应
 */
export interface AuthConfigResponse {
	api_max_request_duration?: number | null;
	db_max_pool_size?: number | null;
	db_max_pool_size_unit?: "connections" | "percent" | null;
	disable_signup?: boolean | null;
	external_anonymous_users_enabled?: boolean | null;
	external_apple_additional_client_ids?: string | null;
	external_apple_client_id?: string | null;
	external_apple_email_optional?: boolean | null;
	external_apple_enabled?: boolean | null;
	external_apple_secret?: string | null;
	external_azure_client_id?: string | null;
	external_azure_email_optional?: boolean | null;
	external_azure_enabled?: boolean | null;
	external_azure_secret?: string | null;
	external_azure_url?: string | null;
	external_bitbucket_client_id?: string | null;
	external_bitbucket_email_optional?: boolean | null;
	external_bitbucket_enabled?: boolean | null;
	external_bitbucket_secret?: string | null;
	external_discord_client_id?: string | null;
	external_discord_email_optional?: boolean | null;
	external_discord_enabled?: boolean | null;
	external_discord_secret?: string | null;
	external_email_enabled?: boolean | null;
	external_facebook_client_id?: string | null;
	external_facebook_email_optional?: boolean | null;
	external_facebook_enabled?: boolean | null;
	external_facebook_secret?: string | null;
	external_figma_client_id?: string | null;
	external_figma_email_optional?: boolean | null;
	external_figma_enabled?: boolean | null;
	external_figma_secret?: string | null;
	external_github_client_id?: string | null;
	external_github_email_optional?: boolean | null;
	external_github_enabled?: boolean | null;
	external_github_secret?: string | null;
	external_gitlab_client_id?: string | null;
	external_gitlab_email_optional?: boolean | null;
	external_gitlab_enabled?: boolean | null;
	external_gitlab_secret?: string | null;
	external_gitlab_url?: string | null;
	external_google_additional_client_ids?: string | null;
	external_google_client_id?: string | null;
	external_google_email_optional?: boolean | null;
	external_google_enabled?: boolean | null;
	external_google_secret?: string | null;
	external_google_skip_nonce_check?: boolean | null;
	external_kakao_client_id?: string | null;
	external_kakao_email_optional?: boolean | null;
	external_kakao_enabled?: boolean | null;
	external_kakao_secret?: string | null;
	external_keycloak_client_id?: string | null;
	external_keycloak_email_optional?: boolean | null;
	external_keycloak_enabled?: boolean | null;
	external_keycloak_secret?: string | null;
	external_keycloak_url?: string | null;
	external_linkedin_oidc_client_id?: string | null;
	external_linkedin_oidc_email_optional?: boolean | null;
	external_linkedin_oidc_enabled?: boolean | null;
	external_linkedin_oidc_secret?: string | null;
	external_slack_oidc_client_id?: string | null;
	external_slack_oidc_email_optional?: boolean | null;
	external_slack_oidc_enabled?: boolean | null;
	external_slack_oidc_secret?: string | null;
	external_notion_client_id?: string | null;
	external_notion_email_optional?: boolean | null;
	external_notion_enabled?: boolean | null;
	external_notion_secret?: string | null;
	external_phone_enabled?: boolean | null;
	external_slack_client_id?: string | null;
	external_slack_email_optional?: boolean | null;
	external_slack_enabled?: boolean | null;
	external_slack_secret?: string | null;
	external_spotify_client_id?: string | null;
	external_spotify_email_optional?: boolean | null;
	external_spotify_enabled?: boolean | null;
	external_spotify_secret?: string | null;
	external_twitch_client_id?: string | null;
	external_twitch_email_optional?: boolean | null;
	external_twitch_enabled?: boolean | null;
	external_twitch_secret?: string | null;
	external_twitter_client_id?: string | null;
	external_twitter_email_optional?: boolean | null;
	external_twitter_enabled?: boolean | null;
	external_twitter_secret?: string | null;
	external_workos_client_id?: string | null;
	external_workos_enabled?: boolean | null;
	external_workos_secret?: string | null;
	external_workos_url?: string | null;
	external_web3_solana_enabled?: boolean | null;
	external_web3_ethereum_enabled?: boolean | null;
	external_zoom_client_id?: string | null;
	external_zoom_email_optional?: boolean | null;
	external_zoom_enabled?: boolean | null;
	external_zoom_secret?: string | null;
	hook_custom_access_token_enabled?: boolean | null;
	hook_custom_access_token_uri?: string | null;
	hook_custom_access_token_secrets?: string | null;
	hook_mfa_verification_attempt_enabled?: boolean | null;
	hook_mfa_verification_attempt_uri?: string | null;
	hook_mfa_verification_attempt_secrets?: string | null;
	hook_password_verification_attempt_enabled?: boolean | null;
	hook_password_verification_attempt_uri?: string | null;
	hook_password_verification_attempt_secrets?: string | null;
	hook_send_sms_enabled?: boolean | null;
	hook_send_sms_uri?: string | null;
	hook_send_sms_secrets?: string | null;
	hook_send_email_enabled?: boolean | null;
	hook_send_email_uri?: string | null;
	hook_send_email_secrets?: string | null;
	hook_before_user_created_enabled?: boolean | null;
	hook_before_user_created_uri?: string | null;
	hook_before_user_created_secrets?: string | null;
	hook_after_user_created_enabled?: boolean | null;
	hook_after_user_created_uri?: string | null;
	hook_after_user_created_secrets?: string | null;
	jwt_exp?: number | null;
	mailer_allow_unverified_email_sign_ins?: boolean | null;
	mailer_autoconfirm?: boolean | null;
	mailer_otp_exp?: number;
	mailer_otp_length?: number | null;
	mailer_secure_email_change_enabled?: boolean | null;
	mailer_subjects_confirmation?: string | null;
	mailer_subjects_email_change?: string | null;
	mailer_subjects_invite?: string | null;
	mailer_subjects_magic_link?: string | null;
	mailer_subjects_reauthentication?: string | null;
	mailer_subjects_recovery?: string | null;
	mailer_subjects_password_changed_notification?: string | null;
	mailer_subjects_email_changed_notification?: string | null;
	mailer_subjects_phone_changed_notification?: string | null;
	mailer_subjects_mfa_factor_enrolled_notification?: string | null;
	mailer_subjects_mfa_factor_unenrolled_notification?: string | null;
	mailer_subjects_identity_linked_notification?: string | null;
	mailer_subjects_identity_unlinked_notification?: string | null;
	mailer_templates_confirmation_content?: string | null;
	mailer_templates_email_change_content?: string | null;
	mailer_templates_invite_content?: string | null;
	mailer_templates_magic_link_content?: string | null;
	mailer_templates_reauthentication_content?: string | null;
	mailer_templates_recovery_content?: string | null;
	mailer_templates_password_changed_notification_content?: string | null;
	mailer_templates_email_changed_notification_content?: string | null;
	mailer_templates_phone_changed_notification_content?: string | null;
	mailer_templates_mfa_factor_enrolled_notification_content?: string | null;
	mailer_templates_mfa_factor_unenrolled_notification_content?: string | null;
	mailer_templates_identity_linked_notification_content?: string | null;
	mailer_templates_identity_unlinked_notification_content?: string | null;
	mailer_notifications_password_changed_enabled?: boolean | null;
	mailer_notifications_email_changed_enabled?: boolean | null;
	mailer_notifications_phone_changed_enabled?: boolean | null;
	mailer_notifications_mfa_factor_enrolled_enabled?: boolean | null;
	mailer_notifications_mfa_factor_unenrolled_enabled?: boolean | null;
	mailer_notifications_identity_linked_enabled?: boolean | null;
	mailer_notifications_identity_unlinked_enabled?: boolean | null;
	mfa_max_enrolled_factors?: number | null;
	mfa_totp_enroll_enabled?: boolean | null;
	mfa_totp_verify_enabled?: boolean | null;
	mfa_phone_enroll_enabled?: boolean | null;
	mfa_phone_verify_enabled?: boolean | null;
	mfa_web_authn_enroll_enabled?: boolean | null;
	mfa_web_authn_verify_enabled?: boolean | null;
	mfa_phone_otp_length?: number;
	mfa_phone_template?: string | null;
	mfa_phone_max_frequency?: number | null;
	password_hibp_enabled?: boolean | null;
	password_min_length?: number | null;
	password_required_characters?: PasswordRequiredCharacters | null;
	rate_limit_anonymous_users?: number | null;
	rate_limit_email_sent?: number | null;
	rate_limit_sms_sent?: number | null;
	rate_limit_token_refresh?: number | null;
	rate_limit_verify?: number | null;
	rate_limit_otp?: number | null;
	rate_limit_web3?: number | null;
	refresh_token_rotation_enabled?: boolean | null;
	saml_enabled?: boolean | null;
	saml_external_url?: string | null;
	saml_allow_encrypted_assertions?: boolean | null;
	security_captcha_enabled?: boolean | null;
	security_captcha_provider?: CaptchaProvider | null;
	security_captcha_secret?: string | null;
	security_manual_linking_enabled?: boolean | null;
	security_refresh_token_reuse_interval?: number | null;
	security_update_password_require_reauthentication?: boolean | null;
	sessions_inactivity_timeout?: number | null;
	sessions_single_per_user?: boolean | null;
	sessions_tags?: string | null;
	sessions_timebox?: number | null;
	site_url?: string | null;
	sms_autoconfirm?: boolean | null;
	sms_max_frequency?: number | null;
	sms_messagebird_access_key?: string | null;
	sms_messagebird_originator?: string | null;
	sms_otp_exp?: number | null;
	sms_otp_length?: number;
	sms_provider?: SmsProvider | null;
	sms_template?: string | null;
	sms_test_otp?: string | null;
	sms_test_otp_valid_until?: string | null;
	sms_textlocal_api_key?: string | null;
	sms_textlocal_sender?: string | null;
	sms_twilio_account_sid?: string | null;
	sms_twilio_auth_token?: string | null;
	sms_twilio_content_sid?: string | null;
	sms_twilio_message_service_sid?: string | null;
	sms_twilio_verify_account_sid?: string | null;
	sms_twilio_verify_auth_token?: string | null;
	sms_twilio_verify_message_service_sid?: string | null;
	sms_vonage_api_key?: string | null;
	sms_vonage_api_secret?: string | null;
	sms_vonage_from?: string | null;
	smtp_admin_email?: string | null;
	smtp_host?: string | null;
	smtp_max_frequency?: number | null;
	smtp_pass?: string | null;
	smtp_port?: string | null;
	smtp_sender_name?: string | null;
	smtp_user?: string | null;
	uri_allow_list?: string | null;
}

/**
 * 更新 Auth 配置请求体
 * 所有字段都是可选的，只更新提供的字段
 */
export interface UpdateAuthConfigBody {
	site_url?: string;
	disable_signup?: boolean;
	jwt_exp?: number;
	smtp_admin_email?: string;
	smtp_host?: string;
	smtp_port?: string;
	smtp_user?: string;
	smtp_pass?: string;
	smtp_max_frequency?: number;
	smtp_sender_name?: string;
	mailer_allow_unverified_email_sign_ins?: boolean;
	mailer_autoconfirm?: boolean;
	mailer_subjects_invite?: string;
	mailer_subjects_confirmation?: string;
	mailer_subjects_recovery?: string;
	mailer_subjects_email_change?: string;
	mailer_subjects_magic_link?: string;
	mailer_subjects_reauthentication?: string;
	mailer_subjects_password_changed_notification?: string;
	mailer_subjects_email_changed_notification?: string;
	mailer_subjects_phone_changed_notification?: string;
	mailer_subjects_mfa_factor_enrolled_notification?: string;
	mailer_subjects_mfa_factor_unenrolled_notification?: string;
	mailer_subjects_identity_linked_notification?: string;
	mailer_subjects_identity_unlinked_notification?: string;
	mailer_templates_invite_content?: string;
	mailer_templates_confirmation_content?: string;
	mailer_templates_recovery_content?: string;
	mailer_templates_email_change_content?: string;
	mailer_templates_magic_link_content?: string;
	mailer_templates_reauthentication_content?: string;
	mailer_templates_password_changed_notification_content?: string;
	mailer_templates_email_changed_notification_content?: string;
	mailer_templates_phone_changed_notification_content?: string;
	mailer_templates_mfa_factor_enrolled_notification_content?: string;
	mailer_templates_mfa_factor_unenrolled_notification_content?: string;
	mailer_templates_identity_linked_notification_content?: string;
	mailer_templates_identity_unlinked_notification_content?: string;
	mailer_notifications_password_changed_enabled?: boolean;
	mailer_notifications_email_changed_enabled?: boolean;
	mailer_notifications_phone_changed_enabled?: boolean;
	mailer_notifications_mfa_factor_enrolled_enabled?: boolean;
	mailer_notifications_mfa_factor_unenrolled_enabled?: boolean;
	mailer_notifications_identity_linked_enabled?: boolean;
	mailer_notifications_identity_unlinked_enabled?: boolean;
	mfa_max_enrolled_factors?: number;
	uri_allow_list?: string;
	external_anonymous_users_enabled?: boolean;
	external_email_enabled?: boolean;
	external_phone_enabled?: boolean;
	saml_enabled?: boolean;
	saml_external_url?: string;
	security_captcha_enabled?: boolean;
	security_captcha_provider?: CaptchaProvider;
	security_captcha_secret?: string;
	sessions_timebox?: number;
	sessions_inactivity_timeout?: number;
	sessions_single_per_user?: boolean;
	sessions_tags?: string;
	rate_limit_anonymous_users?: number;
	rate_limit_email_sent?: number;
	rate_limit_sms_sent?: number;
	rate_limit_verify?: number;
	rate_limit_token_refresh?: number;
	rate_limit_otp?: number;
	rate_limit_web3?: number;
	mailer_secure_email_change_enabled?: boolean;
	refresh_token_rotation_enabled?: boolean;
	password_hibp_enabled?: boolean;
	password_min_length?: number;
	password_required_characters?: PasswordRequiredCharacters;
	security_manual_linking_enabled?: boolean;
	security_update_password_require_reauthentication?: boolean;
	security_refresh_token_reuse_interval?: number;
	mailer_otp_exp?: number;
	mailer_otp_length?: number;
	sms_autoconfirm?: boolean;
	sms_max_frequency?: number;
	sms_otp_exp?: number;
	sms_otp_length?: number;
	sms_provider?: SmsProvider;
	sms_messagebird_access_key?: string;
	sms_messagebird_originator?: string;
	sms_test_otp?: string;
	sms_test_otp_valid_until?: string;
	sms_textlocal_api_key?: string;
	sms_textlocal_sender?: string;
	sms_twilio_account_sid?: string;
	sms_twilio_auth_token?: string;
	sms_twilio_content_sid?: string;
	sms_twilio_message_service_sid?: string;
	sms_twilio_verify_account_sid?: string;
	sms_twilio_verify_auth_token?: string;
	sms_twilio_verify_message_service_sid?: string;
	sms_vonage_api_key?: string;
	sms_vonage_api_secret?: string;
	sms_vonage_from?: string;
	sms_template?: string;
	hook_mfa_verification_attempt_enabled?: boolean;
	hook_mfa_verification_attempt_uri?: string;
	hook_mfa_verification_attempt_secrets?: string;
	hook_password_verification_attempt_enabled?: boolean;
	hook_password_verification_attempt_uri?: string;
	hook_password_verification_attempt_secrets?: string;
	hook_custom_access_token_enabled?: boolean;
	hook_custom_access_token_uri?: string;
	hook_custom_access_token_secrets?: string;
	hook_send_sms_enabled?: boolean;
	hook_send_sms_uri?: string;
	hook_send_sms_secrets?: string;
	hook_send_email_enabled?: boolean;
	hook_send_email_uri?: string;
	hook_send_email_secrets?: string;
	hook_before_user_created_enabled?: boolean;
	hook_before_user_created_uri?: string;
	hook_before_user_created_secrets?: string;
	hook_after_user_created_enabled?: boolean;
	hook_after_user_created_uri?: string;
	hook_after_user_created_secrets?: string;
	// OAuth 提供者配置
	external_apple_enabled?: boolean;
	external_apple_client_id?: string;
	external_apple_email_optional?: boolean;
	external_apple_secret?: string;
	external_apple_additional_client_ids?: string;
	external_azure_enabled?: boolean;
	external_azure_client_id?: string;
	external_azure_email_optional?: boolean;
	external_azure_secret?: string;
	external_azure_url?: string;
	external_bitbucket_enabled?: boolean;
	external_bitbucket_client_id?: string;
	external_bitbucket_email_optional?: boolean;
	external_bitbucket_secret?: string;
	external_discord_enabled?: boolean;
	external_discord_client_id?: string;
	external_discord_email_optional?: boolean;
	external_discord_secret?: string;
	external_facebook_enabled?: boolean;
	external_facebook_client_id?: string;
	external_facebook_email_optional?: boolean;
	external_facebook_secret?: string;
	external_figma_enabled?: boolean;
	external_figma_client_id?: string;
	external_figma_email_optional?: boolean;
	external_figma_secret?: string;
	external_github_enabled?: boolean;
	external_github_client_id?: string;
	external_github_email_optional?: boolean;
	external_github_secret?: string;
	external_gitlab_enabled?: boolean;
	external_gitlab_client_id?: string;
	external_gitlab_email_optional?: boolean;
	external_gitlab_secret?: string;
	external_gitlab_url?: string;
	external_google_enabled?: boolean;
	external_google_client_id?: string;
	external_google_email_optional?: boolean;
	external_google_secret?: string;
	external_google_additional_client_ids?: string;
	external_google_skip_nonce_check?: boolean;
	external_kakao_enabled?: boolean;
	external_kakao_client_id?: string;
	external_kakao_email_optional?: boolean;
	external_kakao_secret?: string;
	external_keycloak_enabled?: boolean;
	external_keycloak_client_id?: string;
	external_keycloak_email_optional?: boolean;
	external_keycloak_secret?: string;
	external_keycloak_url?: string;
	external_linkedin_oidc_enabled?: boolean;
	external_linkedin_oidc_client_id?: string;
	external_linkedin_oidc_email_optional?: boolean;
	external_linkedin_oidc_secret?: string;
	external_slack_oidc_enabled?: boolean;
	external_slack_oidc_client_id?: string;
	external_slack_oidc_email_optional?: boolean;
	external_slack_oidc_secret?: string;
	external_notion_enabled?: boolean;
	external_notion_client_id?: string;
	external_notion_email_optional?: boolean;
	external_notion_secret?: string;
	external_slack_enabled?: boolean;
	external_slack_client_id?: string;
	external_slack_email_optional?: boolean;
	external_slack_secret?: string;
	external_spotify_enabled?: boolean;
	external_spotify_client_id?: string;
	external_spotify_email_optional?: boolean;
	external_spotify_secret?: string;
	external_twitch_enabled?: boolean;
	external_twitch_client_id?: string;
	external_twitch_email_optional?: boolean;
	external_twitch_secret?: string;
	external_twitter_enabled?: boolean;
	external_twitter_client_id?: string;
	external_twitter_email_optional?: boolean;
	external_twitter_secret?: string;
	external_workos_enabled?: boolean;
	external_workos_client_id?: string;
	external_workos_secret?: string;
	external_workos_url?: string;
	external_zoom_enabled?: boolean;
	external_zoom_client_id?: string;
	external_zoom_email_optional?: boolean;
	external_zoom_secret?: string;
	// MFA 配置
	mfa_totp_enroll_enabled?: boolean;
	mfa_totp_verify_enabled?: boolean;
	mfa_phone_enroll_enabled?: boolean;
	mfa_phone_verify_enabled?: boolean;
	mfa_web_authn_enroll_enabled?: boolean;
	mfa_web_authn_verify_enabled?: boolean;
	mfa_phone_otp_length?: number;
	mfa_phone_template?: string;
	mfa_phone_max_frequency?: number;
}

// ============ API 方法 ============

/**
 * 设置遗留签名密钥
 */
export function createLegacySigningKey(ref: string): Promise<ApiResponse<SigningKey>> {
	return request.post<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys/legacy`
	);
}

/**
 * 获取遗留签名密钥信息
 */
export function getLegacySigningKey(ref: string): Promise<ApiResponse<SigningKey>> {
	return request.get<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys/legacy`
	);
}

/**
 * 创建新的签名密钥
 */
export function createSigningKey(
	ref: string,
	data: CreateSigningKeyBody
): Promise<ApiResponse<SigningKey>> {
	return request.post<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys`,
		data
	);
}

/**
 * 获取所有签名密钥
 */
export function listSigningKeys(
	ref: string
): Promise<ApiResponse<SigningKeysResponse>> {
	return request.get<SigningKeysResponse>(
		`/v1/projects/${ref}/config/auth/signing-keys`
	);
}

/**
 * 获取指定签名密钥信息
 */
export function getSigningKey(
	ref: string,
	keyId: string
): Promise<ApiResponse<SigningKey>> {
	return request.get<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys/${keyId}`
	);
}

/**
 * 更新签名密钥状态
 */
export function updateSigningKey(
	ref: string,
	keyId: string,
	data: UpdateSigningKeyBody
): Promise<ApiResponse<SigningKey>> {
	return request.patch<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys/${keyId}`,
		data
	);
}

/**
 * 删除签名密钥
 */
export function deleteSigningKey(
	ref: string,
	keyId: string
): Promise<ApiResponse<SigningKey>> {
	return request.delete<SigningKey>(
		`/v1/projects/${ref}/config/auth/signing-keys/${keyId}`
	);
}

/**
 * 获取项目 Auth 配置
 */
export function getAuthConfig(
	ref: string
): Promise<ApiResponse<AuthConfigResponse>> {
	return request.get<AuthConfigResponse>(
		`/v1/projects/${ref}/config/auth`
	);
}

/**
 * 更新项目 Auth 配置
 */
export function updateAuthConfig(
	ref: string,
	data: UpdateAuthConfigBody
): Promise<ApiResponse<AuthConfigResponse>> {
	return request.patch<AuthConfigResponse>(
		`/v1/projects/${ref}/config/auth`,
		data
	);
}

export default {
	createLegacySigningKey,
	getLegacySigningKey,
	createSigningKey,
	listSigningKeys,
	getSigningKey,
	updateSigningKey,
	deleteSigningKey,
	getAuthConfig,
	updateAuthConfig
};
